#include "delay.h"


uint32_t fac_us=168;
uint32_t fac_ms=168000;


/*
 *  SysTick_CLK参数: HCLK/ HCLK_Div8
 */
void delay_init(uint32_t SysTick_CLK)
{
    // 配置时钟分频
    fac_us = 168;
    fac_ms = 168000;
    SysTick->CTRL |= HCLK;
    if(SysTick_CLK == HCLK_Div8)
    {
        SysTick->CTRL &= HCLK_Div8;
        fac_us /= 8;
        fac_ms /= 8;
    }
    // 清空寄存器
    SysTick->LOAD = SysTick->VAL = 0;
    // 关闭定时器和更新中断
    SysTick->CTRL &= ~(SysTick_CTRL_TICKINT_Msk | SysTick_CTRL_ENABLE_Msk);
}


// 毫秒延迟
void delay_ms(uint32_t xms)
{
    uint32_t count = (xms * fac_ms) / 0xFFFF;
    uint32_t remain = (xms * fac_ms) % 0xFFFF;
    // 清空计数寄存器,关闭定时器
    SysTick->VAL = 0;
    SysTick->CTRL &= ~SysTick_CTRL_ENABLE_Msk;
    // 设置重装值
    SysTick->LOAD = 0xFFFF;
    while(count--)
    {
        // 开启定时器
        SysTick->CTRL |= SysTick_CTRL_ENABLE_Msk;
        // 等待重装,读到1后自动更新为0
//        while(!(SysTick->CTRL & (1ul << 16)));
        while(!(SysTick->CTRL & SysTick_CTRL_COUNTFLAG_Msk));
        // 关闭定时器
        SysTick->CTRL &= ~SysTick_CTRL_ENABLE_Msk;
    }
    if(remain)
    {
        SysTick->VAL = 0;
        SysTick->LOAD = remain;
        // 开启定时器
        SysTick->CTRL |= SysTick_CTRL_ENABLE_Msk;
        // 等待重装,读到1后自动更新为0
//        while(!(SysTick->CTRL & (1ul << 16)));
        while(!(SysTick->CTRL & SysTick_CTRL_COUNTFLAG_Msk));
        // 关闭定时器
        SysTick->CTRL &= ~SysTick_CTRL_ENABLE_Msk;
    }
}


// 微秒延迟
void delay_us(uint32_t xus)
{
    uint32_t count = (xus * fac_us) / 0xFFFF;
    uint32_t remain = (xus * fac_us) % 0xFFFF;
    // 清空计数寄存器,关闭定时器
    SysTick->VAL = 0;
    SysTick->CTRL &= ~SysTick_CTRL_ENABLE_Msk;
    // 设置重装值
    SysTick->LOAD = 0xFFFF;
    while(count--)
    {
        // 开启定时器
        SysTick->CTRL |= SysTick_CTRL_ENABLE_Msk;
        // 等待重装,读到1后自动更新为0
//        while(!(SysTick->CTRL & (1ul << 16)));
        while(!(SysTick->CTRL & SysTick_CTRL_COUNTFLAG_Msk));
        // 关闭定时器
        SysTick->CTRL &= ~SysTick_CTRL_ENABLE_Msk;
    }
    if(remain)
    {
        SysTick->VAL = 0;
        SysTick->LOAD = remain;
        // 开启定时器
        SysTick->CTRL |= SysTick_CTRL_ENABLE_Msk;
        // 等待重装,读到1后自动更新为0
//        while(!(SysTick->CTRL & (1ul << 16)));
        while(!(SysTick->CTRL & SysTick_CTRL_COUNTFLAG_Msk));
        // 关闭定时器
        SysTick->CTRL &= ~SysTick_CTRL_ENABLE_Msk;
    }
}